import 'dart:math';
import 'dart:typed_data';
import 'dart:ui';

import 'package:flutter/cupertino.dart';
import 'package:flutter/material.dart';

class BaseShapePainter extends CustomPainter{
   late Paint _paint;
   double step = 20;//小格边长

   BaseShapePainter(){
     _paint = Paint()
       ..style = PaintingStyle.stroke
       ..color = Colors.grey
       ..strokeWidth = .5;
   }

  @override
  void paint(Canvas canvas, Size size) {
    // TODO: implement paint
    canvas.translate(size.width/2 , size.height/2 );
    _drawGrid(canvas,size);//网格
    //_drawRawPoints(canvas);
    _drawAxis(canvas, size);

    ///矩形自定义
    //_drawRect(canvas);
    //_drawRRect(canvas);
    //_drawDRRect(canvas);
    _drawArcDetail(canvas);
  }

  //直角矩形
   void _drawRect(Canvas canvas){
     _paint ..style = PaintingStyle.fill..color = Colors.blue;

     //矩形中心构造
     Rect rectFromCenter = Rect.fromCenter(center: Offset(0,0), width: 160, height: 160);
     canvas.drawRect(rectFromCenter, _paint);
     //矩形左上右下构造
     Rect rectFromLTRB = Rect.fromLTRB(-120, -120, -80, -80);
     canvas.drawRect(rectFromLTRB, _paint..color = Colors.red);
     //矩形左上宽高构造
     Rect rectFromLTWH = Rect.fromLTWH(80, -120, 40, 40);
     canvas.drawRect(rectFromLTWH, _paint..color = Colors.orange);
      //矩形内切圆构造
     Rect rectFromCircle = Rect.fromCircle(center: Offset(100, 100), radius: 20);
     canvas.drawRect(rectFromCircle, _paint..color = Colors.green);
     //矩形两点构造(对角两个点)
     Rect rectFromPoints = Rect.fromPoints(Offset(-120, 80), Offset(-80, 120));
     canvas.drawRect(rectFromPoints, _paint..color = Colors.purple);
   }

   //圆角矩形
   void _drawRRect(Canvas canvas){
     _paint ..style = PaintingStyle.fill..color = Colors.blue;

     //矩形中心构造(根据xy画弧度)
     Rect rectFromCenter = Rect.fromCenter(center: Offset(0,0), width: 160, height: 160);
     canvas.drawRRect(RRect.fromRectXY(rectFromCenter, 40, 40), _paint);
     //矩形左上右下构造
     RRect rectFromLTRB = RRect.fromLTRBXY(-120, -120, -80, -80,10,10);
     canvas.drawRRect(rectFromLTRB, _paint..color = Colors.red);
     //矩形左上右下构造(直接设置角度值)
     RRect rectFromLTWH = RRect.fromLTRBR(120, -120, 80, -80,Radius.circular(10));
     canvas.drawRRect(rectFromLTWH, _paint..color = Colors.orange);
     //【4】. 圆角矩形fromLTRBAndCorners构造
     canvas.drawRRect(
         RRect.fromLTRBAndCorners(80, 80, 120, 120,
             bottomRight: Radius.elliptical(10, 10)),
         _paint..color = Colors.green);
     //【5】. 矩形两点构造
     Rect rectFromPoints = Rect.fromPoints(Offset(-120, 80), Offset(-80, 120));
     canvas.drawRRect(
         RRect.fromRectAndCorners(rectFromPoints,
             bottomLeft: Radius.elliptical(10, 10)),
         _paint..color = Colors.purple);

   }

   //绘制矩形差域
   void _drawDRRect(Canvas canvas){
     _paint
       ..color = Colors.blue
       ..style = PaintingStyle.fill
       ..strokeWidth = 1.5;
     Rect outRect = Rect.fromCenter(center: Offset(0,0), width: 160, height: 160);
     Rect inRect = Rect.fromCenter(center: Offset(0,0), width: 100, height: 100);

     canvas.drawDRRect(RRect.fromRectXY(outRect, 20, 20), RRect.fromRectXY(inRect, 20, 20), _paint);

     Rect outRect2 =
     Rect.fromCenter(center: Offset(0, 0), width: 60, height: 60);
     Rect inRect2 =
     Rect.fromCenter(center: Offset(0, 0), width: 40, height: 40);
     canvas.drawDRRect(RRect.fromRectXY(outRect2, 15, 15),
         RRect.fromRectXY(inRect2, 10, 10), _paint..color=Colors.green);
   }

   //
   void _drawArcDetail(Canvas canvas){
     var rect = Rect.fromCenter(center: Offset(0, 0), height: 100, width: 100);

     _paint
       ..style = PaintingStyle.stroke
       ..color = Colors.green
       ..strokeWidth = 2;

     canvas.save();
     canvas.translate(-200, 0);
     canvas.drawArc(rect, 0, pi/2  * 3, true, _paint);
     canvas.restore();
   }

  //画轴
   void _drawAxis(Canvas canvas, Size size){
     _paint ..strokeWidth = 1.5 ..color = Colors.black;
     canvas.drawLine(Offset(-size.width/2,0), Offset(size.width/2,0), _paint);
     canvas.drawLine(Offset(0,-size.height/2), Offset(0,size.height/2), _paint);
     canvas.drawLine(Offset( 0,size.height/2) , Offset( 0-7.0,size.height/2-10),_paint);
     canvas.drawLine(Offset( 0,size.height/2) , Offset( 0+7.0,size.height/2-10),_paint);
     canvas.drawLine(Offset(size.width/2,0), Offset(size.width/2-10,0+7), _paint);
     canvas.drawLine(Offset(size.width/2,0), Offset(size.width/2-10,0-7), _paint);

   }
   void _drawRawLines(Canvas canvas) {
     Float32List pos = Float32List.fromList([
       -120, -20,-80, -80,-40,
       -40,0, -100,40, -140,
       80, -160,120, -100]);
     _paint
       ..color = Colors.red
       ..style = PaintingStyle.stroke
       ..strokeWidth = 10
       ..strokeCap = StrokeCap.round;
     canvas.drawRawPoints(PointMode.points, pos, _paint);
   }

  void _drawRawPoints(Canvas canvas) {
    _drawRawLines(canvas);
    Float32List pos = Float32List.fromList([
      -120, -20,-80, -80,-40,
      -40,0, -100,40, -140,
      80, -160,120, -100]);
    _paint
      ..color = Colors.red
      ..style = PaintingStyle.stroke
      ..strokeWidth = 1
      ..strokeCap = StrokeCap.round;
    canvas.drawRawPoints(PointMode.polygon, pos, _paint);
  }

   _drawGrid(Canvas canvas, Size size){
     _drawBottomRight(canvas,size);

     canvas.save();
     canvas.scale(1, -1); //沿x轴镜像
     _drawBottomRight(canvas, size);
     canvas.restore();

     canvas.save();
     canvas.scale(-1, 1); //沿y轴镜像
     _drawBottomRight(canvas, size);
     canvas.restore();

     canvas.save();
     canvas.scale(-1, -1); //沿原点镜像
     _drawBottomRight(canvas, size);
     canvas.restore();
   }

   //初步画网格线
   _drawBottomRight(Canvas canvas, Size size){
     canvas.save();
     for(int i = 0;i < size.height/2/step;i++){
       canvas.drawLine(Offset(0,0), Offset(size.width/2, 0), _paint);
       canvas.translate(0, step);
     }
     canvas.restore();

     canvas.save();
     for(int i = 0;i < size.width/2/step;i++){
       canvas.drawLine(Offset(0,0), Offset(0, size.height/2), _paint);
       canvas.translate(step, 0);
     }
     canvas.restore();
   }

  @override
  bool shouldRepaint(covariant CustomPainter oldDelegate) {
    // TODO: implement shouldRepaint
    return true;
  }

}